#include <math.h>

#include <Columns/ColumnSketchBinary.h>

#include <DataTypes/DataTypeFactory.h>
#include <DataTypes/DataTypeSketchBinary.h>
#include <Formats/ProtobufWriter.h>
#include <DataTypes/Serializations/SerializationSketch.h>

#include <IO/ReadHelpers.h>
#include <IO/WriteHelpers.h>
#include <IO/VarInt.h>

#include <IO/ReadBufferFromString.h>

#ifdef __SSE2__
#include <emmintrin.h>
#endif

#include <Poco/Base64Decoder.h>
#include <Poco/Base64Encoder.h>
#include <Poco/MemoryStream.h>
#include <Poco/StreamCopier.h>

namespace DB
{

namespace ErrorCodes
{
    extern const int INCORRECT_DATA;
}

Field DataTypeSketchBinary::getDefault() const
{
    return String();
}

MutableColumnPtr DataTypeSketchBinary::createColumn() const
{
    return ColumnSketchBinary::create();
}


bool DataTypeSketchBinary::equals(const IDataType & rhs) const
{
    return typeid(rhs) == typeid(*this);
}


SerializationPtr DataTypeSketchBinary::doGetDefaultSerialization() const
{
    return std::make_shared<SerializationSketch>();
}

void registerDataTypeSketchBinary(DataTypeFactory & factory)
{
    auto creator = static_cast<DataTypePtr(*)()>([] { return DataTypePtr(std::make_shared<DataTypeSketchBinary>()); });

    factory.registerSimpleDataType("SketchBinary", creator);

    /// These synonyms are added for compatibility.

    factory.registerAlias("HllSketchBinary", "SketchBinary", DataTypeFactory::CaseInsensitive);
    factory.registerAlias("Base64ToBinary", "SketchBinary", DataTypeFactory::CaseInsensitive);
}

Field DataTypeSketchBinary::stringToVisitorField(const String& ins) const
{
    return stringToVisitorString(ins);
}


String DataTypeSketchBinary::stringToVisitorString(const String & ins) const
{
    // This routine assume ins was generated by FieldVisitorToString, and should be Quoted.
    ReadBufferFromString rb(ins);

    FieldType res;
    readQuoted(res, rb);
    return res;
}

}
